home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1993…ch: Other People's Memory / ADC Developer CD (1993-03) (''Other People's Memory'')_iso / Dev.CD Mar 93.iso / Technical Documentation / Sample Code / DTS.Lib & Samples / DTS.Chat / Menu.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-10-22  |  11.3 KB  |  476 lines  |  [TEXT/MPS ]

  1. /*
  2. ** Apple Macintosh Developer Technical Support
  3. **
  4. ** File:        Menu.c
  5. ** Written by:    Eric Soldan
  6. **
  7. ** Copyright © 1990-1991 Apple Computer, Inc.
  8. ** All rights reserved.
  9. */
  10.  
  11. /* This file manages the application menus. */
  12.  
  13.  
  14.  
  15. /*****************************************************************************/
  16.  
  17.  
  18.  
  19. #include "App.h"            /* Get the application includes/typedefs, etc.    */
  20. #include "App.Common.h"        /* Get the stuff in common with rez.            */
  21. #include "App.protos.h"        /* Get the prototypes for application.            */
  22.  
  23. #ifndef __DESK__
  24. #include <Desk.h>
  25. #endif
  26.  
  27. #ifndef __ERRORS__
  28. #include <Errors.h>
  29. #endif
  30.  
  31. #ifndef __LISTCONTROL__
  32. #include "ListControl.h"
  33. #endif
  34.  
  35. #ifndef __MEMORY__
  36. #include <Memory.h>
  37. #endif
  38.  
  39. #ifndef __MENUS__
  40. #include <Menus.h>
  41. #endif
  42.  
  43. #ifndef __TEXTEDITCONTROL__
  44. #include "TextEditControl.h"
  45. #endif
  46.  
  47. #ifndef __TOOLUTILS__
  48. #include <ToolUtils.h>
  49. #endif
  50.  
  51. #ifndef __UTILITIES__
  52. #include "Utilities.h"
  53. #endif
  54.  
  55.  
  56.  
  57. /*****************************************************************************/
  58.  
  59.  
  60.  
  61. extern Boolean    gQuitApplication;
  62. extern Boolean    gHasAppleEvents;
  63.     /* Above are DTS.Lib..framework globals. */
  64.  
  65. static Boolean    DoAdjustFileMenu(WindowPtr window);
  66. static Boolean    DoAdjustEditMenu(WindowPtr window);
  67. static Boolean    DoAdjustCommunicateMenu(WindowPtr window);
  68.  
  69. #define kMinBlockOfRam 0x10000L
  70.  
  71.  
  72.  
  73. /*****************************************************************************/
  74. /*****************************************************************************/
  75.  
  76.  
  77.  
  78. /* •• Called by DTS.Lib..framework. •• */
  79.  
  80. /* Enable and disable menus based on the current state.  The user can only
  81. ** select enabled menu items.  We set up all the menu items before calling
  82. ** MenuSelect or MenuKey, since these are the only times that a menu item can
  83. ** be selected.  Note that MenuSelect is also the only time the user will see
  84. ** menu items.  This approach to deciding what enable/disable state a menu
  85. ** item has the advantage of concentrating all the decision-making in one
  86. ** place, as opposed to being spread throughout the application.  Other
  87. ** application designs may take a different approach that is just as valid. */
  88.  
  89. #pragma segment Menu
  90. void    DoAdjustMenus(void)
  91. {
  92.     WindowPtr    window;
  93.     Boolean        redrawMenuBar;
  94.  
  95.     window = FrontWindow();
  96.  
  97.     redrawMenuBar  = DoAdjustFileMenu(window);
  98.     redrawMenuBar |= DoAdjustEditMenu(window);
  99.     redrawMenuBar |= DoAdjustCommunicateMenu(window);
  100.  
  101.     if (redrawMenuBar)
  102.         DrawMenuBar();
  103. }
  104.  
  105.  
  106.  
  107. /*****************************************************************************/
  108.  
  109.  
  110.  
  111. /* •• Called by DTS.Lib..framework. •• */
  112.  
  113. /* This is called when an item is chosen from the menu bar (after calling
  114. ** MenuSelect or MenuKey).  It performs the right operation for each command.
  115. ** It is good to have both the result of MenuSelect and MenuKey go to one
  116. ** routine like this to keep everything organized. */
  117.  
  118. #pragma segment Menu
  119. void    DoMenuCommand(long menuResult)
  120. {
  121.     short        menuID, menuItem, daRefNum, saveMode;
  122.     Str255        daName;
  123.     FileRecHndl    frHndl, newFrHndl;
  124.     WindowPtr    window;
  125.     OSErr        err;
  126.  
  127.     if (window = FrontWindow())
  128.         frHndl = (FileRecHndl)GetWRefCon(window);
  129.             /* frHndl is valid only if it is one of our windows. */
  130.  
  131.     menuID = HiWord(menuResult);    /* Use macros for efficiency to get */
  132.     menuItem = LoWord(menuResult);    /* menu item number and menu number. */
  133.  
  134.     switch (menuID) {
  135.  
  136.         case mApple:
  137.             switch (menuItem) {
  138.                 case iAbout:    /* Bring up alert for About. */
  139.                     CenteredAlert(rAboutAlert, nil, (ModalFilterProcPtr)AlertFilter);
  140.                     break;
  141.                 default:        /* All non-About items in this menu are DAs. */
  142.                     GetItem(GetMHandle(mApple), menuItem, daName);
  143.                     daRefNum = OpenDeskAcc(daName);
  144.                     break;
  145.             }
  146.             break;
  147.  
  148.         case mFile:
  149.             switch (menuItem) {
  150.                 case iNew:
  151.                     err = NewDocument(&frHndl, kDocFileType, true);
  152.                     if (!err) {
  153.                         err = DoNewWindow(frHndl, nil, FrontWindow(), (WindowPtr)-1);
  154.                         if (err)
  155.                             DisposeDocument(frHndl);
  156.                     }
  157.                     if (err)
  158.                         CenteredAlert(rErrorAlert, nil, (ModalFilterProcPtr)AlertFilter);
  159.                     break;
  160.                 case iOpen:
  161.                     err = OpenDocument(&frHndl, nil, fsRdWrPerm);
  162.                     if (!err) {
  163.                         err = DoNewWindow(frHndl, nil, FrontWindow(), (WindowPtr)-1);
  164.                         if (err)
  165.                             DisposeDocument(frHndl);
  166.                     }
  167.                     if ((err) && (err != userCanceledErr))
  168.                         CenteredAlert(rErrorAlert, nil, (ModalFilterProcPtr)AlertFilter);
  169.                     break;
  170.                 case iClose:
  171.                     DisposeOneWindow(window, kClose);
  172.                     break;
  173.                 case iSave:
  174.                 case iSaveAs:
  175.                     saveMode = (menuItem == iSave) ? kSave : kSaveAs;
  176.                     if ((*frHndl)->fileState.refNum == kInvalRefNum)
  177.                         saveMode = kSaveAs;
  178.                     err = SaveDocument(frHndl, window, saveMode);
  179.                     if ((err) && (err != userCanceledErr))
  180.                         CenteredAlert(rErrorAlert, nil, (ModalFilterProcPtr)AlertFilter);
  181.                     break;
  182.                 case iDuplicate:
  183.                     err = DuplicateDocument(frHndl, &newFrHndl);
  184.                     if (!err) {
  185.                         err = DoNewWindow(newFrHndl, nil, FrontWindow(), (WindowPtr)-1);
  186.                         if (err)
  187.                             DisposeDocument(newFrHndl);
  188.                     }
  189.                     if (err)
  190.                         CenteredAlert(rErrorAlert, nil, (ModalFilterProcPtr)AlertFilter);
  191.                     break;
  192.                 case iPageSetup:
  193.                     DoSetCursor(&qd.arrow);
  194.                     PresentStyleDialog(frHndl);
  195.                     break;
  196.                 case iPrint:
  197.                     DoSetCursor(&qd.arrow);
  198.                     err = noErr;
  199.                     if (!(*frHndl)->d.doc.fhInfo.printRecValid)
  200.                         err = PresentStyleDialog(frHndl);
  201.                     if (!err) {
  202.                         err = PrintDocument(frHndl, true, true);
  203.                         PrintDocument(nil, false, false);
  204.                     }
  205.                     if ((err) && (err != userCanceledErr))
  206.                         CenteredAlert(rErrorAlert, nil, (ModalFilterProcPtr)AlertFilter);
  207.                     break;
  208.                 case iQuit:
  209.                     gQuitApplication = DisposeAllWindows();
  210.                     break;
  211.             }
  212.             break;
  213.  
  214.         case mEdit:            /* Call SystemEdit for DA editing & MultiFinder. */
  215.             if (IsAppWindow(window)) {
  216.                 switch (menuItem) {
  217.                     case iUndo:
  218.                     case iCut:
  219.                     case iCopy:
  220.                     case iPaste:
  221.                     case iClear:
  222.                         BeginContent(window);
  223.                         switch ((*frHndl)->fileState.sfType) {
  224.                             case kDocFileType:
  225.                             case kTextFileType:
  226.  
  227.                                 if (menuItem == iUndo)
  228.                                     CTEUndo();
  229.                                 else
  230.                                     CTEClipboard(menuItem - iCut + 2);
  231.  
  232.                                 if (menuItem != iCopy)
  233.                                     SetWindowDirty(window);
  234.  
  235.                                 break;
  236. #if VH_VERSION
  237.                             case kViewHierFileType:
  238.                                 if (menuItem == iUndo)
  239.                                     CTEUndo();
  240.                                 else
  241.                                     CTEClipboard(menuItem - iCut + 2);
  242.                                 break;
  243. #endif
  244.                         }
  245.                         EndContent(window);
  246.                         break;
  247. #if VH_VERSION
  248.                     case iViewHier:
  249.                         err = NewDocument(&frHndl, kViewHierFileType, false);
  250.                         if (!err) {
  251.                             err = DoNewWindow(frHndl, nil, FrontWindow(), (WindowPtr)-1);
  252.                             if (err)
  253.                                 DisposeDocument(frHndl);
  254.                         }
  255.                         if (err)
  256.                             CenteredAlert(rErrorAlert, nil, (ModalFilterProcPtr)AlertFilter);
  257.                         break;
  258. #endif
  259.                 }
  260.             }
  261.             else SystemEdit(menuItem - 1);
  262.             break;
  263.  
  264.         case mCommunicate:
  265.             switch (menuItem) {
  266.                 case iConnectToUser:
  267.                     DoSetCursor(&qd.arrow);
  268.                     if ((*frHndl)->connect.connected)
  269.                         SendMessage(frHndl, kDisconnectMssg);
  270.                     else
  271.                         SendConnect(frHndl, (char *)"\pDTS.Chat");
  272.                     break;
  273.                 case iSendToUser:
  274.                     SendMessage(frHndl, kTextMssg);
  275.                     break;
  276.  
  277.             }
  278.             break;
  279.     }
  280.  
  281.     HiliteMenu(0);        /* Unhighlight what MenuSelect (or MenuKey) hilited. */
  282. }
  283.  
  284.  
  285.  
  286. /*****************************************************************************/
  287.  
  288.  
  289.  
  290. /* This function either enables or disables a menu item. */
  291.  
  292. #pragma segment Menu
  293. void    EnableOrDisableItem(MenuHandle menu, short item, Boolean enable)
  294. {
  295.     if (enable)
  296.         EnableItem(menu, item);
  297.     else
  298.         DisableItem(menu, item);
  299. }
  300.  
  301.  
  302.  
  303. /*****************************************************************************/
  304.  
  305.  
  306.  
  307. #pragma segment Menu
  308. static Boolean    DoAdjustFileMenu(WindowPtr window)
  309. {
  310.     MenuHandle    menu;
  311.     FileRecHndl    frHndl;
  312.     short        i, enableItem;
  313.  
  314.     menu = GetMHandle(mFile);
  315.  
  316.     if (IsDAWindow(window)) {
  317.         for (i = iNew; i < iQuit; ++i) DisableItem(menu, i);
  318.         EnableItem(menu, iClose);    /* Let DAs do a close from the menu. */
  319.         return(false);
  320.     }
  321.  
  322.     EnableItem(menu, iNew);                    /* Set these for the no-windows state. */
  323.     EnableItem(menu, iOpen);
  324.     if (MaxBlock() < kMinBlockOfRam) {
  325.         if (CompactMem(kMinBlockOfRam) < kMinBlockOfRam) {
  326.             DisableItem(menu, iNew);        /* Running low on RAM. */
  327.             DisableItem(menu, iOpen);
  328.         }
  329.     }
  330.  
  331.     DisableItem(menu, iClose);
  332.     DisableItem(menu, iSave);
  333.     DisableItem(menu, iSaveAs);
  334.     DisableItem(menu, iDuplicate);
  335.     DisableItem(menu, iPageSetup);
  336.     DisableItem(menu, iPrint);
  337.  
  338.     if (IsDAWindow(window)) {
  339.         DisableItem(menu, iNew);    /* DAs don't get to do a new. */
  340.         DisableItem(menu, iOpen);    /* DAs don't get to do an open. */
  341.         EnableItem(menu, iClose);    /* Let DAs do a close from the menu. */
  342.     }
  343.  
  344.  
  345.     if (window = FrontWindowOfType(kwIsDocument)) {
  346.         EnableItem(menu, iClose);
  347.         frHndl = (FileRecHndl)GetWRefCon(window);
  348.         if ((*frHndl)->fileState.sfType == kDocFileType) {
  349.             enableItem = GetWindowDirty(window);
  350.             if ((*frHndl)->fileState.refNum == kInvalRefNum)
  351.                 enableItem = true;
  352.             EnableOrDisableItem(menu, iSave, enableItem);
  353.             EnableItem(menu, iSaveAs);
  354.             EnableItem(menu, iDuplicate);
  355.         }
  356.         EnableItem(menu, iPageSetup);
  357.         EnableItem(menu, iPrint);
  358.     }
  359.  
  360.     return(false);
  361. }
  362.  
  363.  
  364.  
  365. /*****************************************************************************/
  366.  
  367.  
  368.  
  369. #pragma segment Menu
  370. static Boolean    DoAdjustEditMenu(WindowPtr window)
  371. {
  372.     MenuHandle        menu;
  373.     Boolean            menuEnabled, redrawMenuBar;
  374.     FileRecHndl        frHndl;
  375.     short            i, j;
  376.     static Boolean    editMenuEnabled = true;
  377.  
  378.     menu = GetMHandle(mEdit);
  379.  
  380.     if (IsDAWindow(window)) {
  381.         EnableItem(menu, iUndo);
  382.         EnableItem(menu, iCut);
  383.         EnableItem(menu, iCopy);
  384.         EnableItem(menu, iPaste);
  385.         EnableItem(menu, iClear);
  386. #if VH_VERSION
  387.         DisableItem(menu, iViewHier);
  388. #endif
  389.         redrawMenuBar   = !editMenuEnabled;
  390.         editMenuEnabled = true;
  391.         return(redrawMenuBar);
  392.     }
  393.  
  394. #if VH_VERSION
  395.     j = iViewHier;
  396. #else
  397.     j = iClear;
  398. #endif
  399.  
  400.     menuEnabled = false;
  401.     for (i = iUndo; i <= j; ++i) DisableItem(menu, i);
  402.     if (IsAppWindow(window)) {
  403.         frHndl = (FileRecHndl)GetWRefCon(window);
  404.         switch ((*frHndl)->fileState.sfType) {
  405.             case kDocFileType:
  406.             case kTextFileType:
  407.                 CTEEditMenu(&menuEnabled, mEdit, iUndo, iCut);
  408.                 EnableItem(menu, iViewHier);
  409.                 menuEnabled = true;
  410.                 break;
  411. #if VH_VERSION
  412.             case kViewHierFileType:
  413.                 CTEEditMenu(&menuEnabled, mEdit, iUndo, iCut);
  414.                 break;
  415. #endif
  416.         }
  417.     }
  418.  
  419.     redrawMenuBar   = (editMenuEnabled != menuEnabled);
  420.     editMenuEnabled = menuEnabled;
  421.     return(redrawMenuBar);
  422. }
  423.  
  424.  
  425.  
  426. /*****************************************************************************/
  427.  
  428.  
  429.  
  430. #pragma segment Menu
  431. static Boolean    DoAdjustCommunicateMenu(WindowPtr window)
  432. {
  433.     MenuHandle        menu;
  434.     Boolean            menuEnabled, redrawMenuBar;
  435.     FileRecHndl        frHndl;
  436.     static Boolean    communicateMenuEnabled = true;
  437.  
  438.     menu = GetMHandle(mCommunicate);        /* Start by disabling everything. */
  439.     menuEnabled = false;
  440.  
  441.     CheckItem(menu, iConnectToUser, false);
  442.     DisableItem(menu, iConnectToUser);
  443.     DisableItem(menu, iSendToUser);
  444.  
  445.     if (IsAppWindow(window)) {
  446.         frHndl = (FileRecHndl)GetWRefCon(window);
  447.         if (!(*frHndl)->fileState.readOnly) {
  448.             if (gHasAppleEvents) {
  449.                 if ((*frHndl)->fileState.sfType == kDocFileType) {
  450.                     EnableItem(menu, iConnectToUser);
  451.                     menuEnabled = true;
  452.                     if ((*frHndl)->connect.connected) {
  453.                         DisableItem(menu, iConnectToUser);
  454.                         EnableItem(menu, iSendToUser);
  455.                     }
  456.                     CheckItem(menu, iConnectToUser, (*frHndl)->connect.connected);
  457.                 }
  458.             }
  459.         }
  460.     }
  461.  
  462.     redrawMenuBar = false;
  463.     if (communicateMenuEnabled != menuEnabled) {
  464.         redrawMenuBar = true;
  465.         if (communicateMenuEnabled = menuEnabled)
  466.             EnableItem(menu, 0);
  467.         else
  468.             DisableItem(menu, 0);
  469.     }
  470.  
  471.     return(redrawMenuBar);
  472. }
  473.  
  474.  
  475.  
  476.